<script lang="ts" setup>
import { Search } from '@element-plus/icons-vue';
import { ref, onMounted, watch, computed } from 'vue';
import { api } from '@/apis';
import { ElMessage } from 'element-plus';
import i18n from '@/i18n';
import { ElEmpty } from 'element-plus';
import lightNull from '@/assets/svgs/light_null.svg';
import DarkNull from '@/assets/svgs/dark_null.svg';
import { storeToRefs } from 'pinia';
import { useChangeThemeStore } from '@/store';
import ActiveModel from '@/views/api/components/ActiveModel.vue';

const { t } = i18n.global;
const activeModelVisible = ref(false);
const activeModelItem = ref({});
const loading = ref(false);

export interface Mcp {
  mcpserviceId: string;
  icon: string;
  name: string;
  author: string;
  description: string;
}

interface McpWithChecked extends Mcp {
  isChecked: boolean;
}

const props = withDefaults(
  defineProps<{
    visible: boolean;
    checkedList?: string[];
  }>(),
  {
    visible: false,
    checkedList: () => [],
  },
);

const emits = defineEmits<{
  (e: 'update:visible', visible: boolean): void;
  (e: 'confirm', mcpList: Mcp[]): void;
}>();

const { theme } = storeToRefs(useChangeThemeStore());

const emptyImg = computed(() =>
  theme.value === 'light' ? lightNull : DarkNull,
);

const mcpList = ref<McpWithChecked[]>([]);

const searchKeyword = ref();

const mcpType = ref('all_select');
const mcpIsActive = ref(<boolean | null>null);
/**
 * 查询MCP服务
 */
async function queryMcpList() {
  const [, res] = await api.getMcpList({
    keyword: searchKeyword.value,
    isActive: mcpIsActive.value,
    isInstall: true,
  });
  if (res) {
    mcpList.value = res.result.services.map((item) => {
      return {
        ...item,
        isChecked: props.checkedList.includes(item.mcpserviceId),
      };
    });
  }
}

function onMcpItemClick(item: McpWithChecked) {
  item.isChecked = !item.isChecked;
}

function onConfirm() {
  const checkedMcpList = mcpList.value.filter((item) => item.isChecked);
  if (checkedMcpList.length > 5) {
    ElMessage.error(t('semantic.max_select_mcp_server', { num: 5 }));
    return;
  }
  emits('confirm', checkedMcpList);
}

watch(
  () => props.checkedList,
  () => {
    mcpList.value = mcpList.value.map((item) => {
      return {
        ...item,
        isChecked: props.checkedList.includes(item.mcpserviceId),
      };
    });
  },
);

onMounted(() => {
  queryMcpList();
});

const handleSearchMcpList = (type: 'all_select' | 'active' | 'not_active') => {
  mcpType.value = type;
  if (type === 'all_select') {
    mcpIsActive.value = null;
  } else {
    if (type === 'active') {
      mcpIsActive.value = true;
    } else {
      mcpIsActive.value = false;
    }
  }
  queryMcpList();
};

async function showActive(item: any) {
  if (item.isActive) {
    loading.value = true;
    onActiveService(item.mcpserviceId, item.isActive);
  } else {
    const [, res] = await api.getMcpServiceDetail(item.mcpserviceId, true);
    if (res) {
      activeModelVisible.value = true;
      activeModelItem.value = res.result;
    }
  }
}

function doActive(form: any) {
  loading.value = true;
  onActiveService(activeModelItem.value.serviceId, false, form);
}

async function onActiveService(
  serviceId: string,
  active: boolean = true,
  mcpEnv?: any,
) {
  const [, res] = await api.activeMcpService(serviceId, !active, mcpEnv);
  if (res) {
    queryMcpList();
    ElMessage.success('Success');
    loading.value = false;
  }
}
</script>
<template>
  <div class="prompt-drawer">
    <el-drawer
      size="700"
      :title="t('semantic.mcp_service')"
      :model-value="visible"
      @close="emits('update:visible', false)"
    >
      <div class="wrapper" v-loading="loading">
        <div class="search">
          <el-input
            class="search-input"
            v-model="searchKeyword"
            :placeholder="t('common.search')"
            @change="queryMcpList"
            :suffix-icon="Search"
            clearable
          ></el-input>
        </div>
        <el-tabs
          v-model="mcpType"
          class="plugin-tabs"
          @tab-click="(tab) => handleSearchMcpList(tab.props.name)"
        >
          <el-tab-pane
            :label="$t('plugin_center.mcp.all_select')"
            name="all_select"
            :lazy="true"
          ></el-tab-pane>
          <el-tab-pane
            :label="$t('plugin_center.mcp.active')"
            name="active"
            :lazy="true"
          ></el-tab-pane>
          <el-tab-pane
            :label="$t('plugin_center.mcp.not_active')"
            name="not_active"
            :lazy="true"
          ></el-tab-pane>
        </el-tabs>
        <div class="mcp-list" v-if="mcpList.length">
          <template v-for="item in mcpList" :key="item.id">
            <div class="mcp-item" @click="onMcpItemClick(item)">
              <el-checkbox
                v-model="item.isChecked"
                :disabled="!item.isActive"
                @click.stop
              />
              <img :src="item.icon" alt="" />
              <div>
                <p>{{ item.name }}</p>
                <p>{{ item.description }}</p>
              </div>
              <el-button
                text
                @click.stop="showActive(item)"
                class="mcp-item-status"
              >
                {{
                  item.isActive
                    ? t('plugin_center.mcp.deactivate')
                    : t('plugin_center.mcp.activate')
                }}
              </el-button>
            </div>
          </template>
        </div>
        <ElEmpty
          v-else
          :image="emptyImg"
          :description="$t('common.null')"
          style="height: 100%"
        />
      </div>

      <template #footer>
        <el-button @click="emits('update:visible', false)">
          {{ t('common.cancel') }}
        </el-button>
        <el-button type="primary" @click="onConfirm">
          {{ t('common.confirm') }}
        </el-button>
      </template>
    </el-drawer>
  </div>
  <ActiveModel
    v-model:visible="activeModelVisible"
    :item="activeModelItem"
    :title="$t('plugin_center.mcp.active_mcp_service')"
    @do-active="doActive"
  />
</template>
<style lang="scss" scoped>
.prompt-drawer {
  :deep(.el-drawer) {
    top: 48px;
    height: calc(100vh - 48px);
    .el-drawer__header {
      color: #000;
      font-weight: 700;
      padding: 24px 24px 16px 24px;
      margin: 0;
    }
    .el-drawer__body {
      padding: 0 24px;
    }
    .el-drawer__footer {
      padding: 0;
      padding: 8px 24px;
      box-shadow: 0 -8px 16px rgba(0, 0, 0, 0.1);
    }
  }

  .wrapper {
    height: calc(100vh - 160px);
    display: flex;
    flex-direction: column;

    .search {
      .search-input {
        :deep(.el-input__suffix-inner) {
          display: flex;
          flex-direction: row-reverse;
          .el-icon:not(:last-child) {
            border-left: 1px solid var(--el-border-color);
            padding-left: 8px;
          }
        }
      }
    }

    .mcp-list {
      flex: 1;
      overflow: scroll;
      scrollbar-width: none;
      -ms-overflow-style: none;
      display: flex;
      flex-direction: column;
      margin: 16px 0;
      gap: 8px;

      .mcp-item-status {
        margin-left: auto;
        padding-left: 16px;
      }

      .mcp-item {
        display: flex;
        align-items: center;
        gap: 8px;
        padding: 16px;
        background-color: var(--el-collapse-header-bg);
        border-radius: 4px;
        cursor: pointer;

        p {
          max-width: 550px;
          white-space: nowrap;
          overflow: hidden;
          text-overflow: ellipsis;
        }

        img {
          width: 40px;
          height: 40px;
          border-radius: 50%;
          margin-left: 6px;
        }
      }
    }
  }
}
</style>
<style>
.plugin-tabs {
  padding-right: 8px;
  --o-tabs-font-size: 14px;
  --o-tabs-item-padding: 5px 16px 0 5px;
  --o-tabs-line-height: 32px;
  --o-tabs-color_active: rgb(99, 149, 253);
}
</style>